package io.gitee.caoxiaoyu97.log;

import org.slf4j.ILoggerFactory;
import org.slf4j.IMarkerFactory;
import org.slf4j.spi.MDCAdapter;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.URL;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.List;
import java.util.stream.Collectors;

/*********************************************************
 * 文件名称：SLF4JServiceProvider.java
 * 系统名称：CXY自定义系统
 * 模块名称：io.gitee.caoxiaoyu97.log
 * 功能说明：log代理
 * 开发人员 @author：caoxy31978
 * 开发时间 @date：2023/7/7 14:38
 * 修改记录：程序版本  修改日期  修改人员  修改单号  修改说明
 *********************************************************/
public class SLF4JServiceProvider implements org.slf4j.spi.SLF4JServiceProvider {

    org.slf4j.spi.SLF4JServiceProvider provider;
    ILoggerFactory loggerFactory;

    public SLF4JServiceProvider() throws Exception {
        provider = getSLF4JServiceProvider();
        loggerFactory = name -> LoggerProxy.getLoggerProxy(provider.getLoggerFactory().getLogger(name));
    }

    private org.slf4j.spi.SLF4JServiceProvider getSLF4JServiceProvider(){
        ClassLoader classLoader = SLF4JServiceProvider.class.getClassLoader();
        List<String> collect = getImplementations(org.slf4j.spi.SLF4JServiceProvider.class, classLoader)
                .stream()
                .filter(className -> className!= null && !"".equals(className.trim()))
                .filter(className -> !SLF4JServiceProvider.class.getName().equals(className))
                .collect(Collectors.toList());
        for (String providerImpl : collect) {
            try {
                return (org.slf4j.spi.SLF4JServiceProvider) classLoader.loadClass(providerImpl).getDeclaredConstructor().newInstance();
            }catch (Exception e){
            }
        }
        System.out.println("无可用日志");
        throw new RuntimeException("无可用日志");

    }

    /**
     * 获取指定接口的所有实现类的名称。
     *
     * @param clazz 指定的接口类。
     * @return 所有实现类的名称。
     */
    public static List<String> getImplementations(Class<?> clazz, ClassLoader classLoader){
        classLoader = classLoader == null ? Thread.currentThread().getContextClassLoader() : classLoader;
        List<String> classNames = new ArrayList<>();
        String serviceFile = "META-INF/services/" + clazz.getName();
        Enumeration<URL> e = null;
        try {
            e = classLoader.getResources(serviceFile);
            while (e.hasMoreElements()) {
                java.net.URL url = e.nextElement();
                try (BufferedReader reader = new BufferedReader(
                        new InputStreamReader(url.openStream(), StandardCharsets.UTF_8))) {
                    String line;
                    while ((line = reader.readLine()) != null) {
                        if (!line.startsWith("#") && !line.isEmpty()) {
                            classNames.add(line);
                        }
                    }
                } catch (IOException x) {
                    // throw new ServiceConfigurationError("Error reading configuration file", x);
                }
            }
        } catch (IOException ex) {
        }
        return classNames;
    }

    @Override
    public ILoggerFactory getLoggerFactory() {
        return loggerFactory;
    }

    @Override
    public IMarkerFactory getMarkerFactory() {
        return provider.getMarkerFactory();
    }

    @Override
    public MDCAdapter getMDCAdapter() {
        return provider.getMDCAdapter();
    }

    @Override
    public String getRequestedApiVersion() {
        return provider.getRequestedApiVersion();
    }

    @Override
    public void initialize() {
        provider.initialize();
    }
}
